package xyz.labmem.core.util.gui.tray

import cn.hutool.log.StaticLog
import javafx.application.Platform
import javafx.stage.Stage
import xyz.labmem.core.base.BaseController
import xyz.labmem.core.reflex.FXApplication
import xyz.labmem.core.util.getResourceFile
import java.awt.*
import java.awt.event.*

/**
 * AWT实现系统托盘
 * @Author lty
 * @Date 2021/9/13 9:42
 */
class AwtSystemTray : SystemTrayInterFace {

    private lateinit var showItem: MenuItem
    private lateinit var exitItem: MenuItem
    private lateinit var trayIcon: TrayIcon
    private var showListener: ActionListener? = null
    private var exitListener: ActionListener? = null
    private var mouseListener: MouseListener? = null

    init {
        try {
            //检查系统是否支持托盘
            if (!SystemTray.isSupported()) {
                //系统托盘不支持
                StaticLog.error(Thread.currentThread().stackTrace[1].className + ":系统托盘不支持")
            } else {
                //执行stage.close()方法,窗口不直接退出
                Platform.setImplicitExit(false)
                showItem = MenuItem("显示/隐藏")
                //菜单项(退出)
                exitItem = MenuItem("退出")
                //此处不能选择ico格式的图片,要使用16*16的png格式的图片
                val url = getResourceFile("SysStatic/icon.jpg").url
                val image = Toolkit.getDefaultToolkit().getImage(url)
                //系统托盘图标
                trayIcon = TrayIcon(image)
                //设置图标尺寸自动适应
                trayIcon.isImageAutoSize = true
                //系统托盘
                val tray = SystemTray.getSystemTray()
                //菜单项(打开)中文乱码的问题是编译器的锅,如果使用IDEA,需要在Run-Edit Configuration在LoginApplication中的VM Options中添加-Dfile.encoding=GBK
                //如果使用Eclipse,需要右键Run as-选择Run Configuration,在第二栏Arguments选项中的VM Options中添加-Dfile.encoding=GBK
                //弹出式菜单组件
                val popup = PopupMenu()
                popup.add(showItem)
                popup.add(exitItem)
                trayIcon.popupMenu = popup
                //鼠标移到系统托盘,会显示提示文本
                trayIcon.toolTip = "LabFXApp™"
                tray.add(trayIcon)
            }
        } catch (e: Exception) {
            //系统托盘添加失败
            StaticLog.error(Thread.currentThread().stackTrace[1].className + ":系统添加失败" + e)
        }
    }

    /**
     * 更改系统托盘所监听的Stage
     */
    override fun listen(controller: BaseController) {
        //行为事件: 点击"打开"按钮,显示窗口
        showListener = ActionListener {
            Platform.runLater {
                StaticLog.info("${this.javaClass.simpleName}:托盘监听到打开按钮 then 显示窗口")
                showStage(controller.stage)
            }
        }
        //行为事件: 点击"退出"按钮, 就退出系统
        exitListener = ActionListener {
            StaticLog.info("${this.javaClass.simpleName}:托盘监听到退出按钮 then System shutdown !")
            FXApplication.close()
        }
        //鼠标行为事件: 单击显示stage
        mouseListener = object : MouseAdapter() {
            override fun mouseClicked(e: MouseEvent) {
                StaticLog.info("${this.javaClass.simpleName}:监听到点击托盘")
                //鼠标左键
                if (e.button == MouseEvent.BUTTON1) {
                    showStage(controller.stage)
                }
            }
        }
        //给菜单项添加事件
        showItem.addActionListener(showListener)
        exitItem.addActionListener(exitListener)
        //给系统托盘添加鼠标响应事件
        trayIcon.addMouseListener(mouseListener)
    }

    /**
     * 点击系统托盘,显示界面(并且显示在最前面,将最小化的状态设为false)
     */
    private fun showStage(stage: Stage) {
        //点击系统托盘,
        Platform.runLater {
            if (stage.isIconified) {
                stage.isIconified = false
            }
            if (stage.isShowing) {
                stage.hide()
            }else
                stage.show()
            stage.toFront()
        }
    }
}

